#ifndef RBTHREAD_H
#define RBTHREAD_H

#include "crossbit/common.h"
#include "crossbit/MemoryImage.h"
#include "crossbit/ProcessorState.h"
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <map>

#define RBFUNCNUM 5 

namespace crossbit {
typedef enum {sem=0,mutex,condvar} LockType;

	typedef enum {running=0,idle,block} ThreadState;

	typedef XTUint32 LockId;
	typedef XTUint32 ThreadId;

	typedef struct _Lock{
		LockType	lock_type;
		LockId		lock_id;
		ThreadId	owner_id;
	} Lock;

	typedef struct _Thread{
		ThreadId	thread_id;
		XTMemAddr	next_SPC;
		ThreadState state;
		LockId	blockBy;
		XTUint32 regs[34];
		XTUint32 fregs[34];
	} Thread;

	typedef struct {
		XTInt32		ori_arg_num;
		XTPStr		ori_func_name;
		XTMemAddr	rb_func_addr;
	}RBFuncIndx;

	class RBThreadManager {
		public:
			RBThreadManager(MemoryImage *rb_mi, ProcessorState *rb_ps);

			//static void RBThreadCreate(RBThreadManager *_this, XTInt32 *thread_id, void *attr, void * (*start_routine)(void*), void *arg);
			static void RBThreadCreate(RBThreadManager *_this, int (*start_routine)(void *), void *child_stack, int flags, void *arg); 
			static void RBThreadCleanupPush(RBThreadManager *_this, void * (*routine)(void*), void *arg);
			static void RBThreadJoin(RBThreadManager *_this, XTInt32 thread_id, void **status);
			static void RBThreadExit(RBThreadManager *_this, void *status);

			static void RBCreateLock(RBThreadManager *_this, int *lock);
			static void RBLock(RBThreadManager *_this, int lock_id);
			static void RBUnLock(RBThreadManager *_this, int lock_id);

			XTMemAddr RBSchedule(XTMemAddr nextSPC, XTMemAddr entry);
			ThreadId pickout();

		private:
			RBThreadManager(const RBThreadManager&);
			RBThreadManager& operator=(const RBThreadManager&);

			std::map<ThreadId,Thread>	thread_tbl;
			std::map<LockId,Lock>		lock_tbl;
			MemoryImage					*rb_memory_image;
			ProcessorState				*rb_processor_state;
			ThreadId	thread_running;
			XTUint32	thread_block;
	};

}

#endif
